/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package entity;

import java.util.HashMap;
import java.io.Serializable;
import enviro.*;
import java.util.ArrayList;
import java.util.Iterator;

/**
 * The DungeonEntity represents an game object belonging to a dungeon and
 * is, therefore, a child of the Enviornment interface.  Dungeon entities can 
 * be used to shape and add definition to the dungeon environment.
 * 
 * @author timon
 */
public class DungeonEntity implements Serializable,Entity{
    
    // <editor-fold defaultstate="collapsed" desc="Member Variables">
    
    private Orientation orientation; // Describes the entity's orientation
    
    private boolean visible; // Denotes the visiblility of this object.
    
    private boolean blocking; // Denotes whether other entities may move through
                              // this DungeonEntity
    
    // Keeps the images for each position
    private HashMap<Orientation, String> orientationImagePaths = 
                new HashMap<Orientation, String>();
    
    // A list of friendly environemnts for this entity
    private ArrayList<EnviroType> friendlyEnvirons = new ArrayList<EnviroType>();
    
    // </editor-fold>
    
    // <editor-fold defaultstate="collapsed" desc="Constructor(s)">
    
    /**
     * CONTSTRUCTOR <br/><br/>
     * 
     * Creates and sets default values for a new instance of a DungeonEntity
     */
    public DungeonEntity() {
        
        // Normalize inputs to prevent nasty null errors
        orientationImagePaths.put(Orientation.NORMAL, "");
        orientationImagePaths.put(Orientation.DEGREES_90, "");
        orientationImagePaths.put(Orientation.DEGREES_180, "");
        orientationImagePaths.put(Orientation.DEGREES_270, "");    
    }
    
    // </editor-fold>
    
    // <editor-fold defaultstate="collapsed" desc="API">
    
    /**
     * Set the image for the entity's given rotation / orientation.
     * 
     * This method is for use during manual creation of a DungeonEntity, 
     * it should not be used by the main running program.
     * 
     * @param path
     *   The path/filename of the .png image
     * @param orientation
     *   The orientation/ rotation of the entity image (progresses clockwise) 
     */
    public void setOrientationImagePath(String path, Orientation orientation)  {                                         
        
        orientationImagePaths.put(orientation, path);
    }
    public void setOrientationImagePaths(HashMap<Orientation, String> oip) {
        orientationImagePaths = oip;
    }
    public String getOrientationImagePath(Orientation orientation) {
        
        return orientationImagePaths.get(orientation);
    }
    
    /**
     * Spawn a unique instance of this object and return to caller
     * 
     * This was built to help avoid problems assigning objects to array
     * (which, if I'm not mistaken, is done by reference - FORCING us
     * to deliver separate instances somehow).
     * 
     * @return 
     *   A carbon copy of this object
     */
    public DungeonEntity spawnInstance() {
        
        DungeonEntity temp = new DungeonEntity();
        
        temp.orientation = orientation;
        temp.visible = visible;
        temp.setOrientationImagePaths(orientationImagePaths);
        temp.isBlocking(blocking);
        temp.isVisible(visible);
        
        return temp;
        
    }
    
    @Override
    /**
     * Place a DungeonEntity object in a given environment
     * 
     * @param enviro
     *   The environment in which to place the given entity.
     * @param position
     *   The position in which to place the given entity.
     * @param entity
     *   The entity which will be placed in the given environment.
     * 
     * @return 
     *   Returns true when the operation is successful.  False if otherwise.
     */
    public boolean place(Environment tile, int[][] position) {
        
        return tile.placeEntity(position, this);
    }
    
    public boolean place(Environment tile) {
        return tile.placeEntity(null, this);
    }
    
    
    //<editor-fold defaultstate="collapsed" desc="Standard Get / Set">
    /** 
    * STANDARD GET / SET METHODS
    */
    @Override
    public Orientation getOrientation() {
        return orientation;
    }
    
    @Override
    public void setOrientation(Orientation orientation) {
        this.orientation = orientation;
    }

    @Override
    public void isVisible(boolean visible) {
        this.visible = visible;
    }
    
    @Override
    public boolean isVisible() {
        return visible;
    }
    
    @Override 
    public void isBlocking(boolean blocking) {
        this.blocking = blocking;
    }
    
    @Override
    public boolean isBlocking() {
        return blocking;
    }
    
    public boolean isFriendlyWith(EnviroType enviroType) {
        
        return friendlyEnvirons.contains(enviroType);
    }
    
    public void setFriendlyEnvirons(ArrayList<EnviroType> list) {
        friendlyEnvirons = list;
    }
    
    public Iterator<EnviroType> getFriendlyEnvirons() {
        return friendlyEnvirons.iterator();
    }
    
    public void setFriendlyWith(EnviroType enviroType) {
        friendlyEnvirons.add(enviroType);
    }
    //</editor-fold>
    
    // </editor-fold>
}
